/**
 * Copyright (c) 2016-2021 by the respective copyright holders.
 * All rights reserved. This program and the accompanying materials
 * are made available under the terms of the Eclipse Public License v1.0
 * which accompanies this distribution, and is available at
 * http://www.eclipse.org/legal/epl-v10.html
 */
package com.zsmartsystems.zigbee.zcl.clusters.price;

import java.util.Calendar;

import javax.annotation.Generated;

import com.zsmartsystems.zigbee.zcl.ZclFieldDeserializer;
import com.zsmartsystems.zigbee.zcl.ZclFieldSerializer;
import com.zsmartsystems.zigbee.zcl.protocol.ZclCommandDirection;
import com.zsmartsystems.zigbee.zcl.protocol.ZclDataType;

/**
 * Publish Block Period Command value object class.
 * <p>
 * Cluster: <b>Price</b>. Command ID 0x01 is sent <b>FROM</b> the server.
 * This command is a <b>specific</b> command used for the Price cluster.
 * <p>
 * The Publish Block Period command is generated in response to receiving a Get Block Period(s)
 * command or when an update to the block tariff schedule is available from the commodity
 * provider. When the Get Block Period(s) command is received over the ZigBee Smart Energy
 * network, the Publish Block Period command(s) should be sent unicast to the requestor. In the
 * case of an update to the block tariff schedule from the commodity provider, the Publish Block
 * Period command should be unicast to all individually registered devices implementing the
 * Price Cluster on the ZigBee Smart Energy network. <br> Devices capable of receiving this
 * command must be capable of storing and supporting two block periods, the current active
 * block and the next block. By supporting two block periods, receiving devices will allow the
 * Publish Block Period command generator to publish the next block information during the
 * current block period.
 * <p>
 * Code is auto-generated. Modifications may be overwritten!
 */
@Generated(value = "com.zsmartsystems.zigbee.autocode.ZigBeeCodeGenerator", date = "2020-12-25T10:11:19Z")
public class PublishBlockPeriodCommand extends ZclPriceCommand {
    /**
     * The cluster ID to which this command belongs.
     */
    public static int CLUSTER_ID = 0x0700;

    /**
     * The command ID.
     */
    public static int COMMAND_ID = 0x01;

    /**
     * Provider ID command message field.
     * <p>
     * An unsigned 32-bit field containing a unique identifier for the commodity provider.
     * This field allows differentiation in deregulated markets where multiple commodity
     * providers may be available.
     */
    private Integer providerId;

    /**
     * Issuer Event ID command message field.
     * <p>
     * Unique identifier generated by the commodity provider. When new block period
     * information is provided that replaces older information for the same period, this
     * field allows devices to determine which information is newer. It is expected that the
     * value contained in this field is a unique number managed by upstream servers or a UTC
     * based time stamp (UTCTime data type) identifying when the Publish Block Period command
     * was issued. Thus, newer block period information will have a value in the Issuer Event ID
     * field that is larger than older block information.
     */
    private Integer issuerEventId;

    /**
     * Block Period Start Time command message field.
     * <p>
     * A UTCTime field to denote the time at which the block tariff period starts. A start time of
     * 0x00000000 is a special time denoting “now”. If the device would send an event with a
     * Start Time of now, adjust the Duration In Minutes field to correspond to the remainder of
     * the event. A start date/time of 0xFFFFFFFF shall cause an existing PublishBlockPeriod
     * command with the same Provider ID and Issuer Event ID to be cancelled (note that, in
     * markets where permanently active price information is required for billing purposes,
     * it is recommended that a replacement/superseding Publish Block Period command is used
     * in place of this cancellation mechanism).
     * <p>
     * Where the Duration Timebase is set to a value other than Minutes, the Duration Control
     * sub field provides further clarification; where Duration Control is set to Start of
     * Timebase, the Block Period Start Time shall be set to 00:00:00 on the applicable date,
     * and where Duration Control is set to End of Timebase, the Block Period Start Time shall be
     * set to 23:59:59 on the applicable date.
     */
    private Calendar blockPeriodStartTime;

    /**
     * Block Period Duration command message field.
     * <p>
     * An unsigned 24-bit field to denote the block tariff period . The duration units are
     * defined by the Block Period Duration Type field. Maximum value (0xFFFFFF) means 'until
     * changed'.
     */
    private Integer blockPeriodDuration;

    /**
     * Block Period Control command message field.
     * <p>
     * Identifies additional control options for the block period event. A value of 0x00
     * indicates field not used. Indicates whether a Price Acknowledgment command shall be
     * returned on receipt of this Publish Block Period command. Repeating Block: Indicates
     * whether a block period repeats on expiry. Note that the interaction between Block and
     * Billing periods is out of scope of this specification.
     */
    private Integer blockPeriodControl;

    /**
     * Block Period Duration Type command message field.
     * <p>
     * An 8-bit bitmap where the least significant nibble is an enumerated sub-field
     * indicating the time base used for the duration, and the most significant nibble is an
     * enumerated sub-field providing duration control
     * <p>
     * Where the Duration Timebase is set to a value other than Minutes, the Duration Control
     * sub field provides further clarification; Start of Timebase indicates that the
     * duration shall run from the START of the respective day, week or month, whereas End of
     * Timebase shall indicate that the duration runs from the END of the respective day, week
     * or month. The Duration Control sub-field shall be set to Not Specified when a timebase of
     * Minutes is in use.
     */
    private Integer blockPeriodDurationType;

    /**
     * Tariff Type command message field.
     * <p>
     * An 8-bit bitmap identifying the type of tariff published in this command. The least
     * significant nibble represents an enumeration of the tariff type (Generation Meters
     * shall use the ‘Received’ Tariff). The most significant nibble is reserved.
     */
    private Integer tariffType;

    /**
     * Tariff Resolution Period command message field.
     * <p>
     * An 8 bit enumeration identifying the resolution period for the block tariff.
     * <p>
     * The Tariff Resolution of Block Period means that the Block Tariff is applied based on
     * calculations to the Block Thresholds defined in the command set without smoothing. The
     * Tariff resolution period of 1 Day means that the application should apply “daily
     * resolution”, with recalculation of the thresholds through the Block Period to achieve
     * the same result for the end of the Block Period but smoothing out the tariff application
     * for the customer. This is described as follows:
     */
    private Integer tariffResolutionPeriod;

    /**
     * Default constructor.
     *
     * @deprecated from release 1.3.0. Use the parameterised constructor instead of the default constructor and setters.
     */
    @Deprecated
    public PublishBlockPeriodCommand() {
        clusterId = CLUSTER_ID;
        commandId = COMMAND_ID;
        genericCommand = false;
        commandDirection = ZclCommandDirection.SERVER_TO_CLIENT;
    }

    /**
     * Constructor providing all required parameters.
     *
     * @param providerId {@link Integer} Provider ID
     * @param issuerEventId {@link Integer} Issuer Event ID
     * @param blockPeriodStartTime {@link Calendar} Block Period Start Time
     * @param blockPeriodDuration {@link Integer} Block Period Duration
     * @param blockPeriodControl {@link Integer} Block Period Control
     * @param blockPeriodDurationType {@link Integer} Block Period Duration Type
     * @param tariffType {@link Integer} Tariff Type
     * @param tariffResolutionPeriod {@link Integer} Tariff Resolution Period
     */
    public PublishBlockPeriodCommand(
            Integer providerId,
            Integer issuerEventId,
            Calendar blockPeriodStartTime,
            Integer blockPeriodDuration,
            Integer blockPeriodControl,
            Integer blockPeriodDurationType,
            Integer tariffType,
            Integer tariffResolutionPeriod) {

        clusterId = CLUSTER_ID;
        commandId = COMMAND_ID;
        genericCommand = false;
        commandDirection = ZclCommandDirection.SERVER_TO_CLIENT;

        this.providerId = providerId;
        this.issuerEventId = issuerEventId;
        this.blockPeriodStartTime = blockPeriodStartTime;
        this.blockPeriodDuration = blockPeriodDuration;
        this.blockPeriodControl = blockPeriodControl;
        this.blockPeriodDurationType = blockPeriodDurationType;
        this.tariffType = tariffType;
        this.tariffResolutionPeriod = tariffResolutionPeriod;
    }

    /**
     * Gets Provider ID.
     * <p>
     * An unsigned 32-bit field containing a unique identifier for the commodity provider.
     * This field allows differentiation in deregulated markets where multiple commodity
     * providers may be available.
     *
     * @return the Provider ID
     */
    public Integer getProviderId() {
        return providerId;
    }

    /**
     * Sets Provider ID.
     * <p>
     * An unsigned 32-bit field containing a unique identifier for the commodity provider.
     * This field allows differentiation in deregulated markets where multiple commodity
     * providers may be available.
     *
     * @param providerId the Provider ID
     * @deprecated as of 1.3.0. Use the parameterised constructor instead to ensure that all mandatory fields are provided.
     */
    @Deprecated
    public void setProviderId(final Integer providerId) {
        this.providerId = providerId;
    }

    /**
     * Gets Issuer Event ID.
     * <p>
     * Unique identifier generated by the commodity provider. When new block period
     * information is provided that replaces older information for the same period, this
     * field allows devices to determine which information is newer. It is expected that the
     * value contained in this field is a unique number managed by upstream servers or a UTC
     * based time stamp (UTCTime data type) identifying when the Publish Block Period command
     * was issued. Thus, newer block period information will have a value in the Issuer Event ID
     * field that is larger than older block information.
     *
     * @return the Issuer Event ID
     */
    public Integer getIssuerEventId() {
        return issuerEventId;
    }

    /**
     * Sets Issuer Event ID.
     * <p>
     * Unique identifier generated by the commodity provider. When new block period
     * information is provided that replaces older information for the same period, this
     * field allows devices to determine which information is newer. It is expected that the
     * value contained in this field is a unique number managed by upstream servers or a UTC
     * based time stamp (UTCTime data type) identifying when the Publish Block Period command
     * was issued. Thus, newer block period information will have a value in the Issuer Event ID
     * field that is larger than older block information.
     *
     * @param issuerEventId the Issuer Event ID
     * @deprecated as of 1.3.0. Use the parameterised constructor instead to ensure that all mandatory fields are provided.
     */
    @Deprecated
    public void setIssuerEventId(final Integer issuerEventId) {
        this.issuerEventId = issuerEventId;
    }

    /**
     * Gets Block Period Start Time.
     * <p>
     * A UTCTime field to denote the time at which the block tariff period starts. A start time of
     * 0x00000000 is a special time denoting “now”. If the device would send an event with a
     * Start Time of now, adjust the Duration In Minutes field to correspond to the remainder of
     * the event. A start date/time of 0xFFFFFFFF shall cause an existing PublishBlockPeriod
     * command with the same Provider ID and Issuer Event ID to be cancelled (note that, in
     * markets where permanently active price information is required for billing purposes,
     * it is recommended that a replacement/superseding Publish Block Period command is used
     * in place of this cancellation mechanism).
     * <p>
     * Where the Duration Timebase is set to a value other than Minutes, the Duration Control
     * sub field provides further clarification; where Duration Control is set to Start of
     * Timebase, the Block Period Start Time shall be set to 00:00:00 on the applicable date,
     * and where Duration Control is set to End of Timebase, the Block Period Start Time shall be
     * set to 23:59:59 on the applicable date.
     *
     * @return the Block Period Start Time
     */
    public Calendar getBlockPeriodStartTime() {
        return blockPeriodStartTime;
    }

    /**
     * Sets Block Period Start Time.
     * <p>
     * A UTCTime field to denote the time at which the block tariff period starts. A start time of
     * 0x00000000 is a special time denoting “now”. If the device would send an event with a
     * Start Time of now, adjust the Duration In Minutes field to correspond to the remainder of
     * the event. A start date/time of 0xFFFFFFFF shall cause an existing PublishBlockPeriod
     * command with the same Provider ID and Issuer Event ID to be cancelled (note that, in
     * markets where permanently active price information is required for billing purposes,
     * it is recommended that a replacement/superseding Publish Block Period command is used
     * in place of this cancellation mechanism).
     * <p>
     * Where the Duration Timebase is set to a value other than Minutes, the Duration Control
     * sub field provides further clarification; where Duration Control is set to Start of
     * Timebase, the Block Period Start Time shall be set to 00:00:00 on the applicable date,
     * and where Duration Control is set to End of Timebase, the Block Period Start Time shall be
     * set to 23:59:59 on the applicable date.
     *
     * @param blockPeriodStartTime the Block Period Start Time
     * @deprecated as of 1.3.0. Use the parameterised constructor instead to ensure that all mandatory fields are provided.
     */
    @Deprecated
    public void setBlockPeriodStartTime(final Calendar blockPeriodStartTime) {
        this.blockPeriodStartTime = blockPeriodStartTime;
    }

    /**
     * Gets Block Period Duration.
     * <p>
     * An unsigned 24-bit field to denote the block tariff period . The duration units are
     * defined by the Block Period Duration Type field. Maximum value (0xFFFFFF) means 'until
     * changed'.
     *
     * @return the Block Period Duration
     */
    public Integer getBlockPeriodDuration() {
        return blockPeriodDuration;
    }

    /**
     * Sets Block Period Duration.
     * <p>
     * An unsigned 24-bit field to denote the block tariff period . The duration units are
     * defined by the Block Period Duration Type field. Maximum value (0xFFFFFF) means 'until
     * changed'.
     *
     * @param blockPeriodDuration the Block Period Duration
     * @deprecated as of 1.3.0. Use the parameterised constructor instead to ensure that all mandatory fields are provided.
     */
    @Deprecated
    public void setBlockPeriodDuration(final Integer blockPeriodDuration) {
        this.blockPeriodDuration = blockPeriodDuration;
    }

    /**
     * Gets Block Period Control.
     * <p>
     * Identifies additional control options for the block period event. A value of 0x00
     * indicates field not used. Indicates whether a Price Acknowledgment command shall be
     * returned on receipt of this Publish Block Period command. Repeating Block: Indicates
     * whether a block period repeats on expiry. Note that the interaction between Block and
     * Billing periods is out of scope of this specification.
     *
     * @return the Block Period Control
     */
    public Integer getBlockPeriodControl() {
        return blockPeriodControl;
    }

    /**
     * Sets Block Period Control.
     * <p>
     * Identifies additional control options for the block period event. A value of 0x00
     * indicates field not used. Indicates whether a Price Acknowledgment command shall be
     * returned on receipt of this Publish Block Period command. Repeating Block: Indicates
     * whether a block period repeats on expiry. Note that the interaction between Block and
     * Billing periods is out of scope of this specification.
     *
     * @param blockPeriodControl the Block Period Control
     * @deprecated as of 1.3.0. Use the parameterised constructor instead to ensure that all mandatory fields are provided.
     */
    @Deprecated
    public void setBlockPeriodControl(final Integer blockPeriodControl) {
        this.blockPeriodControl = blockPeriodControl;
    }

    /**
     * Gets Block Period Duration Type.
     * <p>
     * An 8-bit bitmap where the least significant nibble is an enumerated sub-field
     * indicating the time base used for the duration, and the most significant nibble is an
     * enumerated sub-field providing duration control
     * <p>
     * Where the Duration Timebase is set to a value other than Minutes, the Duration Control
     * sub field provides further clarification; Start of Timebase indicates that the
     * duration shall run from the START of the respective day, week or month, whereas End of
     * Timebase shall indicate that the duration runs from the END of the respective day, week
     * or month. The Duration Control sub-field shall be set to Not Specified when a timebase of
     * Minutes is in use.
     *
     * @return the Block Period Duration Type
     */
    public Integer getBlockPeriodDurationType() {
        return blockPeriodDurationType;
    }

    /**
     * Sets Block Period Duration Type.
     * <p>
     * An 8-bit bitmap where the least significant nibble is an enumerated sub-field
     * indicating the time base used for the duration, and the most significant nibble is an
     * enumerated sub-field providing duration control
     * <p>
     * Where the Duration Timebase is set to a value other than Minutes, the Duration Control
     * sub field provides further clarification; Start of Timebase indicates that the
     * duration shall run from the START of the respective day, week or month, whereas End of
     * Timebase shall indicate that the duration runs from the END of the respective day, week
     * or month. The Duration Control sub-field shall be set to Not Specified when a timebase of
     * Minutes is in use.
     *
     * @param blockPeriodDurationType the Block Period Duration Type
     * @deprecated as of 1.3.0. Use the parameterised constructor instead to ensure that all mandatory fields are provided.
     */
    @Deprecated
    public void setBlockPeriodDurationType(final Integer blockPeriodDurationType) {
        this.blockPeriodDurationType = blockPeriodDurationType;
    }

    /**
     * Gets Tariff Type.
     * <p>
     * An 8-bit bitmap identifying the type of tariff published in this command. The least
     * significant nibble represents an enumeration of the tariff type (Generation Meters
     * shall use the ‘Received’ Tariff). The most significant nibble is reserved.
     *
     * @return the Tariff Type
     */
    public Integer getTariffType() {
        return tariffType;
    }

    /**
     * Sets Tariff Type.
     * <p>
     * An 8-bit bitmap identifying the type of tariff published in this command. The least
     * significant nibble represents an enumeration of the tariff type (Generation Meters
     * shall use the ‘Received’ Tariff). The most significant nibble is reserved.
     *
     * @param tariffType the Tariff Type
     * @deprecated as of 1.3.0. Use the parameterised constructor instead to ensure that all mandatory fields are provided.
     */
    @Deprecated
    public void setTariffType(final Integer tariffType) {
        this.tariffType = tariffType;
    }

    /**
     * Gets Tariff Resolution Period.
     * <p>
     * An 8 bit enumeration identifying the resolution period for the block tariff.
     * <p>
     * The Tariff Resolution of Block Period means that the Block Tariff is applied based on
     * calculations to the Block Thresholds defined in the command set without smoothing. The
     * Tariff resolution period of 1 Day means that the application should apply “daily
     * resolution”, with recalculation of the thresholds through the Block Period to achieve
     * the same result for the end of the Block Period but smoothing out the tariff application
     * for the customer. This is described as follows:
     *
     * @return the Tariff Resolution Period
     */
    public Integer getTariffResolutionPeriod() {
        return tariffResolutionPeriod;
    }

    /**
     * Sets Tariff Resolution Period.
     * <p>
     * An 8 bit enumeration identifying the resolution period for the block tariff.
     * <p>
     * The Tariff Resolution of Block Period means that the Block Tariff is applied based on
     * calculations to the Block Thresholds defined in the command set without smoothing. The
     * Tariff resolution period of 1 Day means that the application should apply “daily
     * resolution”, with recalculation of the thresholds through the Block Period to achieve
     * the same result for the end of the Block Period but smoothing out the tariff application
     * for the customer. This is described as follows:
     *
     * @param tariffResolutionPeriod the Tariff Resolution Period
     * @deprecated as of 1.3.0. Use the parameterised constructor instead to ensure that all mandatory fields are provided.
     */
    @Deprecated
    public void setTariffResolutionPeriod(final Integer tariffResolutionPeriod) {
        this.tariffResolutionPeriod = tariffResolutionPeriod;
    }

    @Override
    public void serialize(final ZclFieldSerializer serializer) {
        serializer.serialize(providerId, ZclDataType.UNSIGNED_32_BIT_INTEGER);
        serializer.serialize(issuerEventId, ZclDataType.UNSIGNED_32_BIT_INTEGER);
        serializer.serialize(blockPeriodStartTime, ZclDataType.UTCTIME);
        serializer.serialize(blockPeriodDuration, ZclDataType.UNSIGNED_24_BIT_INTEGER);
        serializer.serialize(blockPeriodControl, ZclDataType.BITMAP_8_BIT);
        serializer.serialize(blockPeriodDurationType, ZclDataType.BITMAP_8_BIT);
        serializer.serialize(tariffType, ZclDataType.BITMAP_8_BIT);
        serializer.serialize(tariffResolutionPeriod, ZclDataType.ENUMERATION_8_BIT);
    }

    @Override
    public void deserialize(final ZclFieldDeserializer deserializer) {
        providerId = (Integer) deserializer.deserialize(ZclDataType.UNSIGNED_32_BIT_INTEGER);
        issuerEventId = (Integer) deserializer.deserialize(ZclDataType.UNSIGNED_32_BIT_INTEGER);
        blockPeriodStartTime = (Calendar) deserializer.deserialize(ZclDataType.UTCTIME);
        blockPeriodDuration = (Integer) deserializer.deserialize(ZclDataType.UNSIGNED_24_BIT_INTEGER);
        blockPeriodControl = (Integer) deserializer.deserialize(ZclDataType.BITMAP_8_BIT);
        blockPeriodDurationType = (Integer) deserializer.deserialize(ZclDataType.BITMAP_8_BIT);
        tariffType = (Integer) deserializer.deserialize(ZclDataType.BITMAP_8_BIT);
        tariffResolutionPeriod = (Integer) deserializer.deserialize(ZclDataType.ENUMERATION_8_BIT);
    }

    @Override
    public String toString() {
        final StringBuilder builder = new StringBuilder(323);
        builder.append("PublishBlockPeriodCommand [");
        builder.append(super.toString());
        builder.append(", providerId=");
        builder.append(providerId);
        builder.append(", issuerEventId=");
        builder.append(issuerEventId);
        builder.append(", blockPeriodStartTime=");
        builder.append(blockPeriodStartTime);
        builder.append(", blockPeriodDuration=");
        builder.append(blockPeriodDuration);
        builder.append(", blockPeriodControl=");
        builder.append(blockPeriodControl);
        builder.append(", blockPeriodDurationType=");
        builder.append(blockPeriodDurationType);
        builder.append(", tariffType=");
        builder.append(tariffType);
        builder.append(", tariffResolutionPeriod=");
        builder.append(tariffResolutionPeriod);
        builder.append(']');
        return builder.toString();
    }

}
